package com.hzqx.syndata.project.controller;


import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.hzqx.syndata.falsedemo.domain.SysConfig;
import com.hzqx.syndata.falsedemo.service.CmsSubjectService;
import com.hzqx.syndata.falsedemo.service.SysConfigService;
import com.hzqx.syndata.project.domain.Comment;
import com.hzqx.syndata.project.domain.User;
import com.hzqx.syndata.project.service.IPmsBrandService;
import com.hzqx.syndata.result1.Result;
import com.hzqx.syndata.result1.ResultBuilder;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletResponse;
import java.io.*;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.UUID;

/**
 * <p>
 * 品牌表 前端控制器
 * </p>
 *
 * @author zy
 * @since 2020-11-03
 */
@Api(tags = "后台管理端--用户模块")
@RestController
@SuppressWarnings("all")
public class PmsBrandController {

    @Autowired
    IPmsBrandService pmsBrandService;
    @Autowired
    CmsSubjectService cmsSubjectService;
    @Autowired
    SysConfigService sysConfigService;

    @ApiOperation(value = "测试错误接口", notes = "测试错误接口")
    @GetMapping("/index")
    public String getdatas(){
        int a = 1/0;
        return pmsBrandService.list().toString();

    }
    @ApiOperation(value = "测试mybatis-plus返回的list方法", notes = "list方法")
    @GetMapping("/index2")
    public String getdatas2(){
        return cmsSubjectService.list().toString();

    }
    @ApiOperation(value = "测试mybatis-plus自带的分页方法", notes = "测试分页方法")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "page", value = "页码数", required = true),
            @ApiImplicitParam(name = "limit", value = "每页条数", required = true)
    })
    @PostMapping("/index3")
    public Result getdatas3(@RequestParam("page") int page,@RequestParam("limit") int limit){
        Page<SysConfig> page1 = new Page<SysConfig>(page,limit);
        IPage<SysConfig> ipage = sysConfigService.page(page1);
        return ResultBuilder.success(ipage);

    }
    @ApiOperation(value = "测试双数据源整合注释使用结果", notes = "测试双数据源整合注释使用结果")
    @GetMapping("/index4")
    public Result getdatas4(){
        return ResultBuilder.success(sysConfigService.getNum());

    }

    @ApiOperation(value = "测试前后端分离restful接口，get请求需要参数", notes = "测试前后端分离restful接口，get请求需要参数")
    @GetMapping("/getDataNeedParams")
    public String getDataNeedParams(String comment){
        return comment == null ? "no parameter" : comment;

    }
    @ApiOperation(value = "测试前后端分离restful接口，get请求必须需要参数", notes = "测试前后端分离restful接口，get请求必须需要参数")
    @GetMapping("/getDataMustNeedParams")
    public String getDataMustNeedParams(@RequestParam("comment") String comment){
        return comment == null ? "no parameter" : comment;

    }
    /**
     * GET 方式传递参数  多个参数
     * */
    @GetMapping("/get03")
    public String get03(@RequestParam("id") String id,
                        @RequestParam("name") String name,
                        @RequestParam("comment") String comment) {
        System.out.println(id + " " + name + " " + comment);
        return id + " " + name + " " + comment;
    }
    /**
     *  使用对象对参数进行封装，这样在多个参数时，优势很明显。
     *  但是这里无法使用 @RequestParam注解，否则会出错。
     *  @RequestBody只与post请求一起使用
     * */
    @GetMapping("/get04")
    public Comment get04( Comment comment) {
        if (Objects.isNull(comment)) {
            return null;  // 需要对 null 值进行处理
        }
        System.out.println(comment);
        return comment;
    }
    /**
     * 使用对象封装参数要求必须具有一个对象，所以可以使用 Map 来封装，这样可以减少对象的数
     * 量。
     * * */
    @GetMapping("/get05")
    public Map<String, String> get05(@RequestParam Map<String, String> map) {
        map.forEach((k, v) -> {
            System.out.println(k + " --> " + v);
        });
        System.out.println(map.size());
        return map;
    }
    /**
     * 参数和路径结合，适用于单个参数的情况
     * */
    @GetMapping("/get06/{id}")
    public Comment getById(@PathVariable("id") String id) {
        Comment comment = new Comment();
        comment.setAge(id);
        comment.setName("Alfred");
        return comment;
    }
    /**
     * 返回值为二进制
     * 其实这里可以使用 Files.readAllBytes()这个方法，这样就简单了。这里我就不改了，我习惯了使用这种
     * 循环读取的方式，不过确实有点繁琐了。
     * */
    @GetMapping("/get07/{name}")
    public void getFile(@PathVariable("name") String name, HttpServletResponse response) {
        try (OutputStream out = new BufferedOutputStream(response.getOutputStream())) {
            try (InputStream in = new BufferedInputStream(new FileInputStream(new File("D:/list/", name)))) {
                int len = 0;
                byte[] data = new byte[4*1024];
                while ((len = in.read(data)) != -1) {
                    out.write(data, 0, len);
                }
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
    /**
     * POST方式传递参数
     * @return
     * */
    @PostMapping("/post01")
    public String post01(@RequestParam("id") String id,
                         @RequestParam("name") String name,
                         @RequestParam("comment") String comment) {
        System.out.println(id + " " + name + " " + comment);
        return id + " " + name + " " + comment;
    }
    @PostMapping("/post02")
    public Map<String, String> post02(@RequestParam Map<String, String> map) {
        map.forEach((k, v) -> {
            System.out.println(k + " --> " + v);
        });
        return map;
    }
    /**
     * 传递对象数组
     * */
    @PostMapping("/post04")
    public Comment[] post04(@RequestBody Comment[] comments) {
        return comments;
    }
    @PostMapping("/post05")
    public List<Comment> post05(@RequestBody List<Comment> commentList) {
        return commentList;
    }
    /**
     * 传递二进制数据
     * */
    @PostMapping("/upload")
    public String uploadFile(@RequestParam("file") MultipartFile file) {
        if (!file.isEmpty()) {
            String fileName = file.getOriginalFilename();
            try {
                file.transferTo(new File("D:/list/", fileName)); // 对于 SpringBoot 中使用路径还是懵逼！
                return "success";
            } catch (IllegalStateException e) {
                e.printStackTrace();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        return "Fail";
    }

    /**
     *  表单数据，含文本和二进制
     * */
    @PostMapping("/submitInfo01")
    public String submitInfo(@RequestParam("id") String id,
                             @RequestParam("name") String name,
                             @RequestParam("file") MultipartFile file) {

        System.out.println("id: " + id);
        System.out.println("name: " + name);
        System.out.println("fileName: " + file != null ? file.getOriginalFilename() : "null");

        if (!file.isEmpty()) {
            String fileName = file.getOriginalFilename();
            try {
                file.transferTo(new File("D:/list/", name+fileName));
                return "success";
            } catch (IllegalStateException e) {
                e.printStackTrace();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        return "Fail";
    }
    /**
     *    表单数据，含文本和二进制 进一步封装！
     * */
    @PostMapping("/submitInfo02")
    public String submitInfo02(User user) {

        MultipartFile file = user.getFile();
        System.out.println("id: " + user.getId());
        System.out.println("name: " + user.getName());
        System.out.println("fileName: " + user != null ? file.getOriginalFilename() : "null");

        if (!file.isEmpty()) {
            String fileName = file.getOriginalFilename();
            try {
                file.transferTo(new File("D:/list/", fileName));
                return "success";
            } catch (IllegalStateException e) {
                e.printStackTrace();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        return "Fail";
    }
    /**
     * POST以二进制形式传递文件，通常的web表单是做不到的，但是ajax2.0以后是支持的，我们来尝试一下。
     * 注意它和 Multipart的区别，Multipart实际上不只包含文件本身的数据，还有文件的其它的信息，例如刚才获取的文件名。
     * 但是如果以二进制的形式传递，它就是完全的文件数据流，不包含任何其它信息，只有文件本身的二进制数据流。
     *
     * 使用这种形式，只能传输单个文件，无法传输多个文件，因为它只是文件本身的二进制数据，如果是多个的话，
     * 那么谁也别想从一个连续的二进制流中把图片切分出来了。
     * */
    @PostMapping("/binaryFile")
    public String binaryFile(@RequestBody byte[] fileData) {
        try {

            Files.write(Paths.get("D:/list/", UUID.randomUUID().toString() + ".jpg"), fileData);
            return "success";
        } catch (IOException e) {
            e.printStackTrace();
            return e.getMessage();
        }
    }

}
